package com.situ.shoplook.common.util;

import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTCreator;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.interfaces.DecodedJWT;
import com.auth0.jwt.interfaces.JWTVerifier;
import com.situ.shoplook.common.model.Account;

import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneId;
import java.util.Map;
import java.util.Objects;
import java.util.UUID;

/**
 * 功能：
 *
 * @author 千堆雪
 * @version 1.0.0
 * <p>
 * created by 千堆雪 on 2024/8/11, last modified by 千堆雪 on 2024/8/11
 */
public class JwtUtils {
    public static String encode(String user, Map<String, Object> payloads, Instant expireTime, String secret) {
        Objects.requireNonNull(secret, "加密密钥不可为空");

        Instant now = Instant.now();

        JWTCreator.Builder builder = JWT.create();
        if (payloads != null) {
            builder.withPayload(payloads);
        }

        if (expireTime != null) {
            //过期时间
            builder.withExpiresAt(expireTime);
        }

        //颁发时间
        builder.withIssuedAt(now);
        //主题
        builder.withSubject("login");
        //发行人
        builder.withIssuer(user);
        //用户
        builder.withAudience(user);
        builder.withNotBefore(now);
        builder.withJWTId(UUID.randomUUID().toString());
        return builder.sign(Algorithm.HMAC256(secret));
    }

    public static String encode(Account account, int minutes, String secret) {
        if (minutes < 0) {
            throw new RuntimeException("有效时长必须大于等于0");
        }
        Map<String, Object> payloads = Map.of("username", account.getUsername());
        LocalDateTime now = LocalDateTime.now();
        now = now.plusMinutes(minutes);

        return encode(account.getUsername(), payloads, now.atZone(ZoneId.systemDefault()).toInstant(), secret);
    }

    /**
     * 解码
     *
     * @param token  jwt
     * @param secret 密钥
     * @return 解密之后的token
     */
    public static DecodedJWT decode(String token, String secret) {
        JWTVerifier jwtVerifier = JWT.require(Algorithm.HMAC256(secret)).build();
        return jwtVerifier.verify(token);
    }
}
